<template>
  <el-dialog v-model="dialogVisible" title="文件上传" width="50%" draggable>
    <div class="file-tree">
      <el-tree :data="fileTree" node-key="id" default-expand-all :expand-on-click-node="false">
        <template #default="{ node, data }">
          <span class="custom-tree-node">
            <span>
              <el-icon v-if="!data.children"><Document /></el-icon>
              <el-icon v-else><Folder /></el-icon>
              {{ node.label }}
            </span>
            <span>
              <template v-if="!data.children">
                <el-button size="small" type="primary" bg link @click="confirmReplace(data)">
                  <el-icon><RefreshRight /></el-icon>替换
                </el-button>
                <el-button size="small" type="danger" bg link @click="confirmDelete(node, data)">
                  <el-icon><Delete /></el-icon>删除
                </el-button>
              </template>
              <template v-else-if="isBottomLevelFolder(data)">
                <el-upload
                  :http-request="options => customUpload(options, data)"
                  :on-success="(response, file) => handleAddFileSuccess(response, file, data)"
                  :show-file-list="false"
                >
                  <el-button size="small" type="success" bg link>
                    <el-icon><CirclePlus /></el-icon>添加文件
                  </el-button>
                </el-upload>
              </template>
            </span>
          </span>
        </template>
      </el-tree>
    </div>
    <template #footer>
      <span class="dialog-footer">
        <el-button @click="dialogVisible = false">取消</el-button>
        <el-button type="primary" @click="handleUpload">确定</el-button>
      </span>
    </template>
  </el-dialog>
</template>

<script lang="ts" setup>
import { ref, onMounted } from "vue";
import { ElMessageBox, ElMessage } from "element-plus";
import type { TreeNode, UploadFile } from "element-plus";
import { GetFolder, DeleteFile, uploadFile, ReplaceFile } from "@/api/modules/upload";
import { Document, Folder, RefreshRight, Delete, CirclePlus } from "@element-plus/icons-vue";

interface FileNode {
  id: number;
  label: string;
  children?: FileNode[];
  path: string;
}
const fileTree = ref<any>([]);
const dialogVisible = ref(false);

const fetchFolder = () => {
  GetFolder({ folder: "" })
    .then(res => {
      fileTree.value = res.data;
    })
    .catch(err => {
      console.error("Error fetching folder:", err);
    });
};

const confirmReplace = async (data: FileNode) => {
  try {
    await ElMessageBox.confirm(`确定要替换文件 "${data.label}" 吗？`, "确认替换", {
      confirmButtonText: "确定",
      cancelButtonText: "取消",
      type: "warning"
    });

    // 用户确认后，打开文件选择对话框
    const input = document.createElement("input");
    input.type = "file";
    input.onchange = event => {
      const file = (event.target as HTMLInputElement).files?.[0];
      if (file) {
        handleReplace(file, data);
      }
    };
    input.click();
  } catch {
    // 用户取消操作，不做任何处理
  }
};

const handleReplace = async (file: File, data: FileNode) => {
  try {
    const formData = new FormData();
    formData.append("file", file);
    formData.append("filepath", data.path);
    await ReplaceFile(formData);
    fetchFolder();
    ElMessage.success("文件替换成功");
  } catch (error) {
    console.error("Error replacing file:", error);
    ElMessage.error("文件替换失败");
  }
};

const confirmDelete = (node: TreeNode, data: FileNode) => {
  ElMessageBox.confirm(`确定要删除文件 "${data.label}" 吗？`, "确认删除", {
    confirmButtonText: "确定",
    cancelButtonText: "取消",
    type: "warning"
  })
    .then(() => {
      handleDelete(node, data);
    })
    .catch(() => {
      // 用户取消操作，不做任何处理
    });
};

const handleDelete = async (node: TreeNode, data: FileNode) => {
  try {
    await DeleteFile({ folder: data.path });
    ElMessage.success("文件删除成功");
  } catch (err) {
    console.error("Error deleting file:", err);
    ElMessage.error("文件删除失败");
  } finally {
    fetchFolder();
  }
};

const handleUpload = () => {
  console.log("上传文件");
  dialogVisible.value = false;
  // 在这里实现文件上传逻辑
};

const handleAddFileSuccess = (response: any, file: UploadFile, folder: FileNode) => {
  console.log("文件上传成功:", response);
  console.log("上传的文件:", file);
  console.log("目标文件夹:", folder.path);

  fetchFolder();
};

// 判断是否为最底层文件夹
const isBottomLevelFolder = (node: FileNode): boolean => {
  return node.children !== undefined && node.children.every(child => child.children === undefined);
};

// 递归函数，用于构建完整路径
const buildPaths = (nodes: FileNode[], parentPath: string = "") => {
  nodes.forEach(node => {
    node.path = `${parentPath}/${node.label}`.replace(/^\/\//, "/");
    if (node.children) {
      buildPaths(node.children, node.path);
    }
  });
};

const customUpload = async (options: any, folder: FileNode) => {
  const { file, onSuccess, onError } = options;
  try {
    const formData = new FormData();
    formData.append("file", file);
    formData.append("filepath", folder.path);
    const response = await uploadFile(formData);
    onSuccess(response.data);
  } catch (error) {
    onError(error as Error);
  }
};

onMounted(() => {
  fetchFolder();
  buildPaths(fileTree.value);
});

// 打开弹窗
const openDialog = () => {
  dialogVisible.value = true;
};

defineExpose({ openDialog });
</script>

<style lang="scss" scoped>
.dialog-header {
  display: flex;
  align-items: center;
  justify-content: space-between;
}
.file-tree {
  max-height: 400px;
  overflow-y: auto;
}
.custom-tree-node {
  display: flex;
  flex: 1;
  align-items: center;
  justify-content: space-between;
  padding-right: 8px;
  font-size: 14px;
  .el-icon {
    margin-right: 8px;
  }
  .el-button {
    margin-left: 8px;
  }
}
.dialog-footer {
  display: flex;
  justify-content: flex-end;
  .el-button {
    margin-left: 10px;
  }
}
</style>
